package org.footito.android.data.update;

import java.util.ArrayList;
import java.util.concurrent.locks.ReentrantLock;

import org.footito.android.api.RefreshParams;
import org.footito.android.tools.Constants;
import org.footito.android.tools.HomeWakeLock;
import org.footito.android.tools.Log;
import org.footito.android.tools.Settings;

import android.app.AlarmManager;
import android.app.PendingIntent;
import android.app.Service;
import android.content.ComponentName;
import android.content.Context;
import android.content.Intent;
import android.content.ServiceConnection;
import android.net.ConnectivityManager;
import android.net.NetworkInfo;
import android.os.Binder;
import android.os.Bundle;
import android.os.IBinder;

public class UpdateService extends Service implements UpdateTaskListener {
	private final IBinder mBinder = new LocalBinder();
	private RefreshParams params;
	private ArrayList<UpdateTaskListener> listeners = new ArrayList<UpdateTaskListener>();
	static ReentrantLock locker = new ReentrantLock();
	private HomeWakeLock homeLock;

	public UpdateService() {
	}

	@Override
	public IBinder onBind(Intent arg0) {
		return mBinder;
	}

	@Override
	public void onCreate() {
		super.onCreate();

	}

	@Override
	public void onStart(Intent intent, int startId) {
		super.onStart(intent, startId);

		Bundle extras;
		if (intent != null)
			extras = intent.getExtras();

		if (locker.tryLock()) {

			homeLock = HomeWakeLock.getInstance();

			ConnectivityManager mgr = (ConnectivityManager) getSystemService(Context.CONNECTIVITY_SERVICE);
			NetworkInfo netInfo = mgr.getActiveNetworkInfo();
			// mgr.getBackgroundDataSetting()
			if (netInfo != null) {// check if we have a connection
				RefreshParams fireparams;
				if (params == null)
					fireparams = new RefreshParams(Settings.getLastCheck(this), -1, -1, -1);
				else
					fireparams = params;
				UpdateDataTask task = new UpdateDataTask(this, this);
				task.setParams(fireparams);
				task.execute((Void) null);
			} // else do nothing
			else {
				// HomeWakeLock homeLock = HomeWakeLock.getInstance();
				homeLock.releaseLock();
				stopSelf();
			}
		}

	}

	public class LocalBinder extends Binder {
		public UpdateService getService() {
			return UpdateService.this;
		}
	}

	@Override
	public void onComplete(int statusAdded) {
		Log.d("Update completed");
		for (int i = 0; i < listeners.size(); i++) {
			listeners.get(i).onComplete(statusAdded);
		}
		stopSelf();
	}

	@Override
	public void onError() {
		for (int i = 0; i < listeners.size(); i++) {
			listeners.get(i).onError();
		}

	}

	@Override
	public void onProgress(ProgressEvents event, int div) {
		for (int i = 0; i < listeners.size(); i++) {
			listeners.get(i).onProgress(event, div);
		}
	}

	public static boolean bindService(Context context, ServiceConnection conn) {
		Intent intent = new Intent(context, UpdateService.class);
		return context.bindService(intent, conn, Context.BIND_AUTO_CREATE);
	}

	public static void unbindService(Context context, ServiceConnection conn) {
		context.unbindService(conn);
	}

	public static void scheduleService(Context context, int frequencyInHour) {
		unScheduleService(context);
		long frequency = frequencyInHour * Constants.MILLISECONDS_IN_HOUR;
		// frequency = 60000; //FIXME need to be removed

		long timeInMillis = System.currentTimeMillis() + frequency;

		Intent intentService = new Intent(context, BroadcastForService.class);
		PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intentService, 0);

		Log.v("prepare the clock to check the service in " + timeInMillis + " seconds, and every " + frequency);
		AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
		alarmManager.setRepeating(AlarmManager.RTC_WAKEUP, timeInMillis, frequency, pendingIntent);
	}

	public static void unScheduleService(Context context) {
		Intent intentService = new Intent(context, BroadcastForService.class);
		PendingIntent pendingIntent = PendingIntent.getBroadcast(context, 0, intentService, 0);
		AlarmManager alarmManager = (AlarmManager) context.getSystemService(Context.ALARM_SERVICE);
		alarmManager.cancel(pendingIntent);
	}

	public static void startService(Context context) {
		Intent intent = new Intent(context, UpdateService.class);
		// intent.setAction(ACTION);
		context.startService(intent);
	}

	public ComponentName performUpdate(Context context, RefreshParams params) {
		this.params = params;
		Intent intent = new Intent(context, UpdateService.class);
		return context.startService(intent);
	}

	public void addListener(UpdateTaskListener listener) {
		listeners.add(listener);
	}

	public void removeListener(UpdateTaskListener listener) {
		listeners.remove(listener);
	}
}
